#ifndef NANE_SCRIPTMODULE_H
#   define NANE_SCRIPTMODULE_H

#   include "nane/core/SubSystemProduct.h"
#   include "nane/ScriptSystem/ScriptObject.h"
#   include "nane/ScriptSystem/ScriptFunction.h"

namespace nane
{

    class ScriptModule
        : public SubSystemProduct
    {
    public:
        class Implementation;
        ScriptModule( const NullType& = NullPtr );
        ScriptModule( Implementation* _impl );
        ScriptModule( const ScriptModule& _other );

    public:
        ScriptObject ImportObject( const char* _objectName );

        template<typename F>
        bool ExportFunctor( const char* _className, const char* _functionName, F _functor )
        {
            return ExportFunctionImpl_(_className, _functionName, new ScriptFunctionAdapter<F>(_functor));
        }
        
        ScriptObject ExportFunctionInterface( const char* _className, const char* _functionName, IScriptFunction* _cfunction );
        template<typename F>
        bool ExportFunction( const char* _className, const char* _functionName, F _function )
        {
            return ExportFunctor(_className, _functionName, MakeFunctor(_function));
        }
        
        template<typename F, class C>
        bool ExportMemberFunction( const char* _className, const char* _functionName, F _function, C* _object )
        {
            return ExportFunctor(_className, _functionName, MakeMemberFunctor(_function, _object));
        }
        
    private:
        bool ExportFunctionImpl_( const char* _className, const char* _functionName, ScriptFunctionBase* _scriptFunctionBase );

    public:
        Implementation* m;
    };
    
    template<>
    inline bool ScriptModule::ExportFunction<ScriptFunctionBase*>( const char* _className, const char* _functionName, ScriptFunctionBase* _cfunction )
    {
        return ExportFunctionImpl_(_className, _functionName, _cfunction);
    }    
}   // namespace nane

#endif	// NANE_SCRIPTMODULE_H
